package com.sinosoft.platform.common.message.impl;

import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import org.springframework.validation.BindException;
import org.springframework.validation.FieldError;
import org.springframework.validation.ObjectError;

import com.sinosoft.platform.common.message.Message;
import com.sinosoft.platform.common.message.MessageCategory;
import com.sinosoft.platform.common.message.MessageManager;
import com.sinosoft.platform.common.message.RequestStorageManager;
import com.sinosoft.platform.common.util.StringUtil;

/**
 * 
  *【类或接口功能描述】
  *
  * @author WL
  * @date  2011-7-12 
  * @version 1.0
  *
  *【修改描述】
  *
  * @author WL
  * @date  2011-7-12
 */
@SuppressWarnings("unchecked")
public class MessageManagerImpl extends MessageManager {

    /**
     * 获取相应消息类型的消息存储Map 
     * 
     * @param
     * @return
     * @throws
     */
    private Map getMessages(MessageCategory messageCategory) {
        Map messageMap;
        String messageCategoryName = messageCategory.getName();
        if (RequestStorageManager.getInstance().has(messageCategoryName)) {
            messageMap = (Map) RequestStorageManager.getInstance().get(messageCategoryName);
        }
        else {
            messageMap = new LinkedHashMap();
            RequestStorageManager.getInstance().set(messageCategoryName, messageMap);
        }
        return messageMap;
    }

    /**
     * 添加消息
     * 
     * @param
     * @return
     * @throws
     */
    private void addMessage(MessageCategory messageCategory, String messageKey, Object[] messageParameters,
            String messageFieldId, Object rejectValue) {
        Map messageMap = getMessages(messageCategory);

        messageMap.put(messageKey + StringUtil.arrayToDelimited(messageParameters), new Message(messageCategory,
                messageKey, messageParameters, messageFieldId, rejectValue));

    }

    public void addErrorMessage(String messageKey) {
        addErrorMessage(messageKey, null, null);
    }

    public void addErrorMessage(String messageKey, String messageFieldId) {
        addErrorMessage(messageKey, null, messageFieldId, null);

    }

    public void addErrorMessage(String messageKey, Object[] messageParameters) {
        addErrorMessage(messageKey, messageParameters, null, null);
    }

    public void addErrorMessage(String messageKey, Object[] messageParameters, String messageFieldId) {
        addErrorMessage(messageKey, messageParameters, messageFieldId, null);

    }

    public void addErrorMessage(String messageKey, Object[] messageParameters, String messageFieldId, Object rejectValue) {
        addMessage(MessageCategory.ERROR, messageKey, messageParameters, messageFieldId, rejectValue);
    }

    public void addInfoMessage(String messageKey) {
        addInfoMessage(messageKey, null);

    }

    public void addInfoMessage(String messageKey, Object[] messageParameters) {
        addMessage(MessageCategory.INFORMATION, messageKey, messageParameters, null, null);

    }

    public void addWarningMessage(String messageKey) {
        addWarningMessage(messageKey, null);

    }

    public void addWarningMessage(String messageKey, Object[] messageParameters) {
        addMessage(MessageCategory.WARNING, messageKey, messageParameters, null, null);

    }

    public Iterator getErrorMessages() {
        return getMessages(MessageCategory.ERROR).values().iterator();
    }

    public Iterator getInfoMessages() {
        return getMessages(MessageCategory.INFORMATION).values().iterator();
    }

    public Iterator getWarningMessages() {
        return getMessages(MessageCategory.WARNING).values().iterator();
    }

   
	public Iterator getMessages() {
        Map allMessages = new LinkedHashMap();
        allMessages.putAll(getMessages(MessageCategory.ERROR));
        allMessages.putAll(getMessages(MessageCategory.WARNING));
        allMessages.putAll(getMessages(MessageCategory.INFORMATION));
        Iterator allMessageIterator = allMessages.values().iterator();
        return allMessageIterator;
    }

    /**
     * 返回所有信息的键值
     * 
     * @param separator
     */
    public String getMessagesAsString(String separator) {
        StringBuffer buf = new StringBuffer();
        String sep = "";

        // Write Error Messages
        Iterator it = MessageManager.getInstance().getErrorMessages();
        while (it.hasNext()) {
            Message message = (Message) it.next();
            buf.append(sep).append("错误: ").append(message);
            sep = separator;
        }

        // Write Warning Messages
        it = MessageManager.getInstance().getWarningMessages();
        while (it.hasNext()) {
            Message message = (Message) it.next();
            buf.append(sep).append("警告: ").append(message);
            sep = separator;
        }

        // Write Info Messages
        it = MessageManager.getInstance().getInfoMessages();
        while (it.hasNext()) {
            Message message = (Message) it.next();
            buf.append(sep).append("信息: ").append(message);
            sep = separator;
        }
        return buf.toString();
    }

    private boolean hasMessage(MessageCategory messageCategory, String messageKey) {
        Map messageMap = getMessages(messageCategory);
        return messageMap.containsKey(messageKey);
    }

    public boolean hasErrorMessages() {
        return getMessages(MessageCategory.ERROR).size() > 0;
    }

    public boolean hasInfoMessages() {
        return getMessages(MessageCategory.INFORMATION).size() > 0;
    }

    public boolean hasWarningMessages() {
        return getMessages(MessageCategory.WARNING).size() > 0;
    }

    public boolean hasMessage(String messageKey) {
        boolean containKey = false;
        containKey = hasMessage(MessageCategory.ERROR, messageKey);
        if (!containKey) {
            containKey = hasMessage(MessageCategory.WARNING, messageKey);
        }
        if (!containKey) {
            containKey = hasMessage(MessageCategory.INFORMATION, messageKey);
        }
        return containKey;
    }

    public boolean hasMessages() {
        return (hasErrorMessages() || hasWarningMessages() || hasInfoMessages());
    }

    public void addBindingErrorMessages(BindException bindException) {
        if (bindException != null) {
            List errors = bindException.getAllErrors();
            for (int i = 0; i < errors.size(); i++) {
                ObjectError error = (ObjectError) errors.get(i);
                if (error instanceof FieldError) {
                    FieldError fError = (FieldError) error;
                    int errorCodeLength = fError.getCodes().length;
                    int errorCodeIndex = 0;
                    if (errorCodeLength > 1) {
                        errorCodeIndex = errorCodeLength - 2;
                    }
                    addErrorMessage(fError.getCodes()[errorCodeIndex], fError.getArguments(), fError.getField(), fError
                            .getRejectedValue());
                }
                else {
                    addErrorMessage(error.getCode(), error.getArguments());
                }

            }
        }
    }

}
